`timescale 1ns / 1ps

`include "cp0.vh"

module exception(
	input wire rst,
	input wire[8:0] except,
	input wire[31:0] cp0_status,cp0_cause,cp0_epc,
	output wire[31:0] excepttype,newpc,
    output wire flush_and_jump
    );
	
assign excepttype = (rst)? `CP0_NO_EXC:
                    (((cp0_cause[15:8] & cp0_status[15:8]) != 8'h00) &
				 	 ~cp0_status[1] & cp0_status[0])? `CP0_EXC_INT:
                    except[`EXC_SIGNAL_ADELI]? `CP0_EXC_ADEL:
                    except[`EXC_SIGNAL_RI]? `CP0_EXC_RI:
                    except[`EXC_SIGNAL_OV]? `CP0_EXC_OV:
                    except[`EXC_SIGNAL_BP]? `CP0_EXC_BP:
                    except[`EXC_SIGNAL_SYS]? `CP0_EXC_SYS:
                    except[`EXC_SIGNAL_ADELD]? `CP0_EXC_ADEL:
                    except[`EXC_SIGNAL_ADES]? `CP0_EXC_ADES:
                    except[`EXC_SIGNAL_ERET]? `CP0_EXC_ERET:
                    `CP0_NO_EXC;

assign newpc = (excepttype == `CP0_EXC_ERET)? cp0_epc:
                32'hbfc00380;

assign flush_and_jump = excepttype != `CP0_NO_EXC;

endmodule
